home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 2 / Apprentice-Release2.iso / Source Code / Think Class Libraries / Expander / Expander Classes / CExpanderButton.cp < prev    next >
Encoding:
Text File  |  1994-11-30  |  6.1 KB  |  281 lines  |  [TEXT/KAHL]

  1. /***********************************************************************************
  2.     CExpanderButton.h
  3.  
  4.     Copyright © 1994 B-Ray Software. All rights reserved.
  5.     Developed using Symantec C++ 7.0.2 and Symantec's TCL library.
  6.     Portions of this code courtesy Symantec, Inc.
  7.  
  8.     This code may be freely distributed as long as this notice remains. This code
  9.     may not be used in any commercial software without the consent of B-Ray Software.
  10.  
  11.     ---
  12.  
  13.     CExpanderButton is a pane that shows a toggle button much like that found in 
  14.     the Apple's Finder file list and Symantec's Project Manager project window.
  15.     The class supports both color and B&W icons.
  16.  
  17. ***********************************************************************************/
  18. #include <TBUtilities.h>
  19.  
  20. #include "CExpanderButton.h"
  21. #include "ExpanderMessages.h"
  22. #include "CExpander.h"
  23.  
  24.  
  25. #define CICN_BASE            5000    // hardcoded resource ID of ICON's to show - sorry!
  26.  
  27.  
  28. TCL_DEFINE_CLASS_D1( CExpanderButton, CExpanderPane );
  29.  
  30.  
  31. /*
  32.  * NumInstances keeps track of the number of times we have invoked this class. We use it
  33.  * to determine when to create and destroy the icons structure. Otherwise we would have
  34.  * a bunch of them, all the same for each invokation
  35.  */
  36.  
  37. short            CExpanderButton::numInstances = 0;
  38. CIconHandle        CExpanderButton::icons[ kMaxIconIndex ];
  39.  
  40.  
  41. /*
  42.  * CExpanderButton constructor
  43.  *
  44.  * Default constructor - should only be called when created by a file read.
  45.  */
  46.  
  47. CExpanderButton :: CExpanderButton() : CExpanderPane()
  48. {
  49.     IExpanderButton( TRUE );        // obtain our icon handles
  50.  
  51.     TCL_END_CONSTRUCTOR
  52. }
  53.  
  54.  
  55. /*
  56.  * CExpanderButton constructor
  57.  *
  58.  * Normal constructor - should always be called when creating a new
  59.  * CExpanderButton object.
  60.  */
  61.  
  62. CExpanderButton :: CExpanderButton( CView *anEnclosure, CBureaucrat *aSupervisor, short aWidth, short aHeight,
  63.                                     short aHLoc, short aVLoc, SizingOption aHSizing, SizingOption aVSizing,
  64.                                     Boolean useColor )
  65.                     : CExpanderPane( anEnclosure, aSupervisor, aWidth, aHeight, aHLoc, aVLoc, 
  66.                                      aHSizing, aVSizing )
  67. {
  68.     IExpanderButton( useColor );    // obtain our icon handles
  69.  
  70.     TCL_END_CONSTRUCTOR
  71. }
  72.  
  73.  
  74. /*
  75.  * CExpanderButton destructor
  76.  *
  77.  * Frees memory used by our icon handles.
  78.  */
  79.  
  80. CExpanderButton :: ~CExpanderButton()
  81. {
  82.     TCL_START_DESTRUCTOR
  83.  
  84.     --numInstances;
  85.  
  86.     if ( usingColor == TRUE && numInstances == 0 ) {
  87.         short loop;
  88.         for ( loop = 0; loop < kTwirly; ++loop )
  89.             if ( icons[ loop ] )
  90.                 DisposeCIcon( icons[ loop ] );
  91.     }
  92. }
  93.  
  94.  
  95. /*
  96.  * IExanderButton method
  97.  *
  98.  * Private method to setup our button's icons.
  99.  */
  100.  
  101. void CExpanderButton :: IExpanderButton( Boolean useColor )
  102. {
  103.     SetWantsClicks( TRUE );            // we want user clicks
  104.  
  105.     if ( gSystem.hasColorQD && useColor ) {
  106.         short    loop, id;
  107.         usingColor = TRUE;
  108.  
  109.         /*
  110.          * Load color icons if this is the first class object created
  111.          */
  112.         if ( ++numInstances == 1 ) {
  113.             for ( loop = 0; loop < kMaxIconIndex; ++loop ) {
  114.                 id = CICN_BASE + loop;
  115.                 icons[ loop ] = GetCIcon( id );
  116.             }
  117.         }
  118.     }
  119.     else {
  120.         usingColor = FALSE;
  121.     }
  122.  
  123.     value = 0;
  124. }
  125.  
  126.  
  127. /*
  128.  * SetEnabled method
  129.  *
  130.  * Enables/disables our button. Display of button should change with
  131.  * this state change.
  132.  */
  133.  
  134. void CExpanderButton :: SetEnabled( Boolean fEnabled )
  135. {
  136.     SetWantsClicks( fEnabled );        // disable selection by mouse
  137.     Prepare();
  138.     Refresh();                        // cause update to redraw our button
  139. }
  140.  
  141.  
  142. /*
  143.  * SetValue method
  144.  *
  145.  * Changes the value of our button - expanded or unexpanded depending on
  146.  * the value given.
  147.  */
  148.  
  149. void CExpanderButton :: SetValue( Boolean aValue )
  150. {
  151.     value = aValue;                    // save new value
  152.     Prepare();
  153.     Refresh();                        // cause update to redraw our button
  154. }
  155.  
  156.  
  157. /*
  158.  * DrawIcon method
  159.  *
  160.  * Protected method that draws our icon in the pane.
  161.  */
  162.  
  163. void CExpanderButton :: DrawIcon( short index )
  164. {
  165.     Rect    iconRect = { 0, 0, 16, 16 };
  166.  
  167. //    EraseRect( &iconRect );        // not needed if drawing done in copy mode
  168.     if ( usingColor ) {
  169.         PlotCIcon( &iconRect, icons[ index - 1 ] );
  170.     }
  171.     else {
  172.         DrawSICN( CICN_BASE, index, topLeft( iconRect ) );
  173.     }
  174. }
  175.  
  176.  
  177. /*
  178.  * Draw method - OVERRIDE
  179.  *
  180.  * Called in response to an update event in our pane.
  181.  */
  182.  
  183. void CExpanderButton :: Draw( Rect *area )
  184. {
  185.     if ( ! printing )    // don't draw icon when printing - laser printers see it anyway
  186.         DrawIcon( CalcIconIndex() );
  187. }
  188.  
  189.  
  190. /*
  191.  * DoClick method - OVERRIDE
  192.  *
  193.  * Handles mouse down events in the pane. We watch the mouse until the button is
  194.  * released.
  195.  */
  196.  
  197. void CExpanderButton :: DoClick( Point hitPt, short modifierKeys, long when )
  198. {
  199.     Boolean        wasInButton = TRUE;
  200.     Point        where;
  201.     Rect        btnFrame;
  202.     long        dummy;
  203.  
  204.     Prepare();
  205.  
  206.     LongToQDRect( &frame, &btnFrame );        // get frame in QD space
  207.     DrawIcon( CalcIconIndex() + 1 );        // draw the button in hilited state
  208.  
  209.     while ( StillDown() ) {                    // loop until the button is released
  210.         GetMouse( &where );
  211.         if ( PtInRect( where, &btnFrame ) ) {
  212.             if ( !wasInButton ) {            // mouse entered button
  213.                 DrawIcon( CalcIconIndex() + 1 );
  214.                 wasInButton = TRUE;
  215.             }
  216.         }
  217.         else {
  218.             if ( wasInButton ) {            // mouse left button
  219.                 DrawIcon( CalcIconIndex() );
  220.                 wasInButton = FALSE;
  221.             }
  222.         }
  223.     };
  224.  
  225.     if ( wasInButton ) {                    // button released inside pane
  226.         Delay( 2, &dummy );                    // wait a little bit
  227.         EraseRect( &btnFrame );
  228.         DrawIcon( kTwirly );                // draw an intermediate icon to show movement
  229.         Delay( 2, &dummy );                    // wait a little bit more
  230.         EraseRect( &btnFrame );
  231.         DoCommand( value ? cmdUnexpandPane : cmdExpandPane );    // send command for parent to see
  232.     }
  233. }
  234.  
  235.  
  236. /*
  237.  * CalcIconIndex method
  238.  *
  239.  * Private method that calculates the appropriate icon index to use when drawing.
  240.  * Takes into account enabled state and present value of button.
  241.  */
  242.  
  243. short CExpanderButton :: CalcIconIndex( void )
  244. {    
  245.     short    index = kUnexpandedDisabled;
  246.  
  247.     if ( GetWantsClicks() )                    // enabled?
  248.         ++index;
  249.  
  250.     if ( value )                            // selected?
  251.         index += 3;
  252.  
  253.     return index;
  254. }
  255.  
  256.  
  257. /*
  258.  * PutTo method - OVERRIDE
  259.  *
  260.  * Writes to the stream all of the info we need to save.
  261.  */
  262.  
  263. void CExpanderButton :: PutTo( CStream &stream )
  264. {
  265.     stream << value;
  266.     CExpanderPane::PutTo( stream );
  267. }
  268.  
  269.  
  270. /*
  271.  * GetFrom method - OVERRIDE
  272.  *
  273.  * Reads from the stream all of the info that we saved.
  274.  */
  275.  
  276. void CExpanderButton :: GetFrom( CStream &stream )
  277. {
  278.     stream >> value;
  279.     CExpanderPane::GetFrom( stream );
  280. }
  281.